<?php

class FollowModel
{
    private $followKeyPrefix    =   'FI/';
    private $followMeType       =   1;
    private $meFollowType       =   2;
    private $diaryListCacheModel;
    
    public function __construct(){
        $this->diaryListCacheModel    =    new DiaryListCacheModel();
    }

    public function getFollowList ($id, $uid, $type, $start, $length) {
        if (empty($uid)) {
            AC::$errorNo    =   'FWM002';
            return  FALSE;
        }
        
        $key    =   $this->followKeyPrefix. $uid;
        $where  =   " type = ".$type." AND status = 0 ";
        if ($id > 0) {
            $where .= " AND id < ".$id;
        }

        $orderBy=   ' id DESC ';
        $result =   Storage::getConditionManyData($key, $where, $orderBy, $start, $length);
        return  $result;
    }
    
    public function meFollow($info)/*{{{*/
    {
        if (empty($info['uid']) ||  empty($info['fUid']))
        {
            AC::$errorNo    =   'FWM003';
            return  FALSE;
        }

        if ($info['uid'] == $info['fUid'])
        {
            AC::$errorNo    =   'FWM020';
            return  FALSE;
        }
        $time   =   AC::SERVER_TIME;
        isset($info['time'])    &&  $time   =   $info['time'];

        # check follow info     /*{{{*/
        $followInfo     =   $this->getFollowInfo($info);

        if (isset($followInfo['followMe']['status']) || isset($followInfo['meFollow']['status']))
        {
            if (isset($followInfo['followMe']['status']) && AC::FOLLOW_STATUS_BLACK ==  $followInfo['followMe']['status'])
            {
                AC::$errorNo    =   'FWM010';
                return  FALSE;
            }
            if (isset($followInfo['meFollow']['status']))
            {
                if (AC::FOLLOW_STATUS_BLACK ==  $followInfo['meFollow']['status'])
                {
                   # AC::$errorNo    =   'FWM013';
                   # return  FALSE;
                    $meFollowKey    =   $this->followKeyPrefix. $info['uid'];
                    $meFollowWhere  =   array('fUid' => $info['fUid'], 'type' => $this->meFollowType);
                    $meFollowResult =   Storage::delConditionData($meFollowKey, $meFollowWhere);
                                                
                    $followMeKey    =   $this->followKeyPrefix. $info['fUid'];
                    $followMeWhere  =   array('fUid' => $info['uid'], 'type' => $this->followMeType);
                    $followMeResult =   Storage::delConditionData($followMeKey, $followMeWhere);

                    if (empty($meFollowResult))
                     {
                         AC::$errorNo    =   'FWM018';       
                         return  FALSE;
                     }
                    $mod=new UserStatisticsModel();
                    // 删除好友列表
                    $this->diaryListCacheModel->delBlackList($info['uid'], $info['fUid']);
                    $mod->userStatistics(array('uid'=>$info['uid'],'meBlackTimes'=>-1));
                    $mod->userStatistics(array('uid'=>$info['fUid'],'blackMeTimes'=>-1));



                }
                elseif (AC::FOLLOW_STATUS_NORMAL == $followInfo['meFollow']['status'])
                {
                    AC::$errorNo    =   'FWM014';
                    return  FALSE;
                }
            }

            if (AC::FOLLOW_STATUS_DELETE    ==  $followInfo['meFollow']['status'])
            {
                $dataMeFollow   =   array(
                                        'status'    =>  AC::FOLLOW_STATUS_NORMAL,
                                    );
                $meFollowKey    =   $this->followKeyPrefix. $info['uid'];
                $meFollowWhere  =   array('fUid' => $info['fUid'], 'type' => $this->meFollowType);
                $meFollowResult =   Storage::setConditionData($meFollowKey, $dataMeFollow, $meFollowWhere);

                $dataFollowMe   =   array(
                                        'status'    =>  AC::FOLLOW_STATUS_NORMAL,
                                    );
                $followMeWhere  =   array('fUid' => $info['uid'], 'type' => $this->followMeType);
                $followMeKey    =   $this->followKeyPrefix. $info['fUid'];
                $followMeResult =   Storage::setConditionData($followMeKey, $dataFollowMe, $followMeWhere);

                if (($meFollowResult +  $followMeResult) < 1)
                {
                    AC::$errorNo    =   'FWM011';
                    return  FALSE;
                }
                return  TRUE;
            }
            #   return  TRUE;
        }/*}}}*/

        $dataMeFollow   =   array(
                                'uid'   =>  $info['uid'],
                                'fUid'  =>  $info['fUid'],
                                'time'  =>  $time,
                                'type'  =>  $this->meFollowType,
                            );
        $meFollowKey    =   $this->followKeyPrefix. $info['uid'];
        $meFollowResult =   Storage::addData($meFollowKey, $dataMeFollow);
        #   if (empty($meFollowResult))
        #   {
        #       AC::$errorNo    =   'FWM004';
        #       return  FALSE;
        #   }

        # meFollow = other user followMe!
        $dataFollowMe   =   array(
                                'uid'   =>  $info['fUid'],
                                'fUid'  =>  $info['uid'],
                                'time'  =>  $time,
                                'type'  =>  $this->followMeType,
                            );
        $followMeKey    =   $this->followKeyPrefix. $info['fUid'];
        $followMeResult =   Storage::addData($followMeKey, $dataFollowMe);
        #   if (empty($followMeResult))
        #   {
        #       AC::$errorNo    =   'FWM005';
        #       return  FALSE;
        #   }
        return  TRUE;
    }/*}}}*/

    public function countTotal($info)/*{{{*/
    {
        if (empty($info['uid']))
        {
            AC::$errorNo    =   'FWM002';
            return  FALSE;
        }
        $where  =   array('type' => $this->followMeType,'status'=>'0');
        if ($info['type'] == $this->followMeType && $info['status'] == '2'){
            $where  =   array('type' => $this->followMeType,'status'=>$info['status']);
        }
        if (isset($info['type']) && ($this->meFollowType ==  $info['type']))
        {
            $where  =   array('type' => $this->meFollowType,'status' => $info['status']);
        }
        $key    =   $this->followKeyPrefix. $info['uid'];

        $result =   Storage::countDataRow($key, $where);
        return  $result;
    }/*}}}*/

    public function getFollowInfo($info) {
        if (empty($info['uid']) ||  empty($info['fUid']))
        {
            AC::$errorNo    =   'FWM009';
            return  FALSE;
        }
        
        return $this->getUserFollowInfo($info);
        
        $key    =   $this->followKeyPrefix. $info['uid'];
        $where  =   array('fUid' => $info['fUid']);
        $follow =   Storage::getConditionManyData($key, $where);

        $result =   array('followMe' => NULL, 'meFollow' => NULL);
        if (count($follow) > 0  &&  is_array($follow))
        {
            foreach ($follow    as  $value)
            {
                if (empty($value)   ||  empty($value['type']))  continue;

                if ($this->followMeType ==  $value['type']) $result['followMe'] =   $value;
                if ($this->meFollowType ==  $value['type']) $result['meFollow'] =   $value;
            }
        }

        return  $result;
    }/*}}}*/
    
    /**
     * 判断用户与用户之间的关系
     * status 0 表示正常
     * status 2 表示被拉黑
     * @param unknown $info
     * @return boolean|multitype:NULL string
     */
    public function getUserFollowInfo($info){
        
        if (empty($info['uid']) ||  empty($info['fUid']))
        {
            AC::$errorNo    =   'FWM009';
            return  FALSE;
        }
        
        $meFollow    =    $this->diaryListCacheModel->checkIsFriend($info['uid'], $info['fUid']);
        $followMe    =    $this->diaryListCacheModel->checkIsFriend($info['fUid'], $info['uid']);
        $blocked     =    $this->diaryListCacheModel->checkIsBlocked($info['uid'], $info['fUid']);
        $blockedMe   =    $this->diaryListCacheModel->checkIsBlocked($info['fUid'], $info['uid']);
        
        $result =   array('followMe' => NULL, 'meFollow' => NULL);
        $tmp['fUid']    =    $info['fUid'];
        $tmp['status']  =    '0';
        $tmp['uid']     =    $info['uid'];
        if ($followMe) {
            $tmp['type']    =    strval($this->followMeType);
            $result['followMe'] =   $tmp;
        }
        if ($meFollow){
            $tmp['type']    =    strval($this->meFollowType);
            $result['meFollow'] =   $tmp;
        }
        
        if ($blockedMe){
            $tmp['status']    =    '2';
            $tmp['type']    =    strval($this->followMeType);
            $result['followMe'] =   $tmp;
        }
        
        if ($blocked){
            $tmp['status']    =    '2';
            $tmp['type']      =    strval($this->meFollowType);
            $result['meFollow'] =   $tmp;
        }
        
        return $result;
    }
    
    public function removeFollow($info)/*{{{*/
    {
        if (empty($info['uid']) ||  empty($info['fUid']))
        {
            AC::$errorNo    =   'FWM003';
            return  FALSE;
        }

        $followInfo     =   $this->getFollowInfo($info);
        #   if (empty($followInfo['meFollow']))/*{{{*/
        #   {
        #       AC::$errorNo    =   'FWM019';
        #       return  FALSE;
        #   }

        #   if (AC::FOLLOW_STATUS_NORMAL != $followInfo['meFollow']['status'])
        #   {
        #       AC::$errorNo    =   'FWM015';
        #       return  FALSE;
        #   }/*}}}*/

        $meFollowKey    =   $this->followKeyPrefix. $info['uid'];
        $meFollowWhere  =   array('fUid' => $info['fUid'], 'type' => $this->meFollowType);
        $meFollowResult =   Storage::delConditionData($meFollowKey, $meFollowWhere);
        // 删除好友的时候删除缓存备注
        $this->removeRmask($info);
        
        $followMeKey    =   $this->followKeyPrefix. $info['fUid'];
        $followMeWhere  =   array('fUid' => $info['uid'], 'type' => $this->followMeType);
        $followMeResult =   Storage::delConditionData($followMeKey, $followMeWhere);

        #   if (empty($meFollowResult))/*{{{*/
        #   {
        #       AC::$errorNo    =   'FWM007';
        #       return  FALSE;
        #   }
        #   if (empty($followMeResult))
        #   {
        #       AC::$errorNo    =   'FWM008';
        #       return  FALSE;
        #   }/*}}}*/
        if (empty($followInfo['meFollow']))/*{{{*/
        {
            #   AC::$errorNo    =   'FWM019';
            return  FALSE;
        }/*}}}*/
        return  TRUE;
    }/*}}}*/
    
    /**
     * 删除好友的时候将缓存备注清空
     * @param unknown $info
     * @return boolean
     */
    private function removeRmask($info){
        $info['uid']    =    intval($info['uid']);
        $info['fUid']   =    intval($info['fUid']);
        if ($info['uid'] < 1 || $info['fUid'] < 1){
            return FALSE;
        }
        $list =  $this->diaryListCacheModel->getRmask($info['uid']);
        if (empty($list) && !isset($list[$info['fUid']])){
            return FALSE;
        }
        unset($list[$info['fUid']]);
        $this->diaryListCacheModel->addRmask($info['uid'], $list);
        
        return TRUE;
    }
    
    public function removeFans($info)/*{{{*/
    {
        if (empty($info['uid']) ||  empty($info['fUid']))
        {
            AC::$errorNo    =   'FWM020';
            return  FALSE;
        }

        $followInfo     =   $this->getFollowInfo($info);
        #   if (empty($followInfo['followMe']))/*{{{*/
        #   {
        #       AC::$errorNo    =   'FWM021';
        #       return  FALSE;
        #   }

        #   if (AC::FOLLOW_STATUS_NORMAL != $followInfo['followMe']['status'])
        #   {
        #       AC::$errorNo    =   'FWM022';
        #       return  FALSE;
        #   }/*}}}*/

        $meFollowKey    =   $this->followKeyPrefix. $info['fUid'];
        $meFollowWhere  =   array('fUid' => $info['uid'], 'type' => $this->meFollowType);
        $meFollowResult =   Storage::delConditionData($meFollowKey, $meFollowWhere);

        $followMeKey    =   $this->followKeyPrefix. $info['uid'];
        $followMeWhere  =   array('fUid' => $info['fUid'], 'type' => $this->followMeType);
        $followMeResult =   Storage::delConditionData($followMeKey, $followMeWhere);

        #   if (empty($meFollowResult))/*{{{*/
        #   {
        #       AC::$errorNo    =   'FWM023';
        #       return  FALSE;
        #   }
        #   if (empty($followMeResult))
        #   {
        #       AC::$errorNo    =   'FWM024';
        #       return  FALSE;
        #   }/*}}}*/
        if (empty($followInfo['followMe']))/*{{{*/
        {
            #   AC::$errorNo    =   'FWM021';
            return  FALSE;
        }/*}}}*/
        return  TRUE;
    }/*}}}*/

    public function isBlackMe($info)/*{{{*/
    {
        #   uid =   HOST_UID;
        #   fUid=   access HOME/userInfo-uid or Diary-uid or xxxList-uid ...
        if ($info['uid'] == $info['fUid'])  return  FALSE;

        $result =   $this->getFollowInfo($info);
        if (!empty($result['followMe']['status'])   &&  (AC::FOLLOW_STATUS_BLACK ==  $result['followMe']['status']))
        {
            AC::$errorNo    =   'FWM025';
            return  TRUE;
        }

        return  FALSE;
    }/*}}}*/

    public function getBlacklist($info)/*{{{*/
    {
        if (empty($info['uid']))
        {
            AC::$errorNo    =   'FWM002';
            return  FALSE;
        }

        $key    =   $this->followKeyPrefix. $info['uid'];
        $where  =   array('type' => $this->meFollowType, 'status' => 2);
        $orderBy=   ' id DESC ';
        $result =   Storage::getConditionManyData($key, $where, $orderBy);
        return  $result;
    }/*}}}*/

    public function blacklistFollow($info)/*{{{*/
    {
        if (empty($info['uid']) ||  empty($info['fUid']))
        {
            AC::$errorNo    =   'FWM003';
            return  FALSE;
        }

        if ($info['uid'] == $info['fUid'])
        {
            AC::$errorNo    =   'FWM020';
            return  FALSE;
        }

        $followInfo =   $this->getFollowInfo($info);

        if (empty($followInfo['meFollow'])) {
            $dataMeFollow   =   array(
                                    'uid'       =>  $info['uid'],
                                    'fUid'      =>  $info['fUid'],
                                    'time'      =>  AC::SERVER_TIME,
                                    'type'      =>  $this->meFollowType, 
                                    'status'    =>  AC::FOLLOW_STATUS_BLACK,
                                );
            $meFollowKey    =   $this->followKeyPrefix. $info['uid'];
            $meFollowResult =   Storage::addData($meFollowKey, $dataMeFollow);

            $dataFollowMe   =   array(
                                    'uid'       =>  $info['fUid'],
                                    'fUid'      =>  $info['uid'],
                                    'time'      =>  AC::SERVER_TIME,
                                    'type'      =>  $this->followMeType,
                                    'status'    =>  AC::FOLLOW_STATUS_BLACK,
                                );
            $followMeKey    =   $this->followKeyPrefix. $info['fUid'];
            $followMeResult =   Storage::addData($followMeKey, $dataFollowMe);

            return  TRUE;
        }

        if (AC::FOLLOW_STATUS_BLACK ==  $followInfo['meFollow']['status'])
        {
            AC::$errorNo    =   'FWM017';
            return  FALSE;
        }

        $data   =   array('status' => AC::FOLLOW_STATUS_BLACK);

        $meFollowKey    =   $this->followKeyPrefix. $info['uid'];
        $meFollowWhere  =   array('fUid' => $info['fUid'], 'type' => $this->meFollowType);
        $meFollowResult =   Storage::setConditionData($meFollowKey, $data, $meFollowWhere);

        $followMeKey    =   $this->followKeyPrefix. $info['fUid'];
        $followMeWhere  =   array('fUid' => $info['uid'], 'type' => $this->followMeType);
        $followMeResult =   Storage::setConditionData($followMeKey, $data, $followMeWhere);

        if (empty($meFollowResult))
        {
            AC::$errorNo    =   'FWM012';
            return  FALSE;
        }

        return  TRUE;
    }/*}}}*/

    public function relieveBlacklist($info)/*{{{*/
    {
        if (empty($info['uid']) ||  empty($info['fUid']))
        {
            AC::$errorNo    =   'FWM003';
            return  FALSE;
        }

        $followInfo     =   $this->getFollowInfo($info);
        if (empty($followInfo['meFollow'])  ||  (AC::FOLLOW_STATUS_BLACK != $followInfo['meFollow']['status']))
        {
            AC::$errorNo    =   'FWM016';
            return  FALSE;
        }

        $meFollowKey    =   $this->followKeyPrefix. $info['uid'];
        $meFollowWhere  =   array('fUid' => $info['fUid'], 'type' => $this->meFollowType);
        $meFollowResult =   Storage::delConditionData($meFollowKey, $meFollowWhere);

        $followMeKey    =   $this->followKeyPrefix. $info['fUid'];
        $followMeWhere  =   array('fUid' => $info['uid'], 'type' => $this->followMeType);
        $followMeResult =   Storage::delConditionData($followMeKey, $followMeWhere);

        if (empty($meFollowResult))
        {
            AC::$errorNo    =   'FWM018';
            return  FALSE;
        }

        return  TRUE;
    }/*}}}*/
    
    /**
     * 获取粉丝列表
     * @param unknown $uid
     * @return boolean|Ambigous <multitype:, boolean, unknown>
     */
    public function getFollowMesList($uid, $no='')/*{{{*/
    {
        if (empty($uid))
        {
            AC::$errorNo    =   'FWM001';
            return  FALSE;
        }
        if (empty($no)){
            $result = $this->diaryListCacheModel->getFansList($uid);
            if(!empty($result)){
                return $result;
            }
        }
        $key    =   $this->followKeyPrefix. $uid;
        $where  =   array('type' => $this->followMeType, 'status' => 0);
        $result =   Storage::getConditionManyData($key, $where);
        $list   =   array();
        if (!empty($result) && is_array($result)){
            $this->diaryListCacheModel->removeFans($uid);
            foreach ($result as $value){
                $this->diaryListCacheModel->addFans($uid, $value['fUid']);
                $list[]    =    $value['fUid'];
            }
        }
        
        return  $list;
    }/*}}}*/
    
    /**
     * 获取好友列表
     * @param unknown $uid
     * @return boolean|Ambigous <multitype:, boolean, unknown>
     */
    public function getMeFollowsList($uid, $no='')/*{{{*/
    {
        if (empty($uid))
        {
            AC::$errorNo    =   'FWM001';
            return  FALSE;
        }
        if (empty($no)){
            $result = $this->diaryListCacheModel->getFriendsList($uid);
            if(!empty($result)){
                return $result;
            }
        }
        
        $key    =   $this->followKeyPrefix. $uid;
        $where  =   array('type' => $this->meFollowType, 'status' => 0);
        $result =   Storage::getConditionManyData($key, $where);
        $list   =   array();
        if (!empty($result) && is_array($result)){
            $this->diaryListCacheModel->removeFriends($uid);
            foreach ($result as $value){
                $this->diaryListCacheModel->addFriends($uid, $value['fUid']);
                $list[]    =    $value['fUid'];
            }
        }
        
        return  $list;
    }/*}}}*/
    
    /**
     * 获取我拉黑的列表
     * @param unknown $info
     * @return boolean|unknown|multitype:Ambigous <>
     */
    public function getMeBlacklist($info, $no='')/*{{{*/
    {
        if (empty($info['uid']))
        {
            AC::$errorNo    =   'FWM002';
            return  FALSE;
        }
        if (empty($no)){
            $result = $this->diaryListCacheModel->getBlackList($info['uid']);
            if(!empty($result)){
                return $result;
            }
        }
        $key    =   $this->followKeyPrefix. $info['uid'];
        $where  =   array('type' => $this->meFollowType, 'status' => 2);
        $orderBy=   ' id DESC ';
        $result =   Storage::getConditionManyData($key, $where, $orderBy);
        $list = array();
        if (!empty($result) && is_array($result)){
	        $this->diaryListCacheModel->removeBlacked($info['uid']);
            foreach ($result as $value){
                $this->diaryListCacheModel->addBlackList($info['uid'], $value['fUid']);
                $list[] = $value['fUid'];
            }
        }
        return  $list;
    }/*}}}*/
    
    /**
     * 设置备注
     * @param unknown $info
     * @return boolean|Ambigous <boolean, unknown>
     */
    public function setFriendsName($info){
        if (intval($info['uid']) < 1 || intval($info['fUid']) < 1){
            AC::$errorNo    =    'FM033';
            return FALSE;
        }
        // 备注名称以及分组限定长度为24个字符
        $data = array();
        $data['remark_name']    =    UK::getstr($info['nickname'], 24,'',1);
        
        $where = array('uid'=>intval($info['uid']),'fUid'=>intval($info['fUid']),'type'=>$this->meFollowType);
        $key   = $this->followKeyPrefix.$info['uid'];
        $result= Storage::setConditionData($key, $data, $where);
        // 没填昵称时则为删除
        if ($data['remark_name'] == ''){
            $this->diaryListCacheModel->removeRmask(AC::HOST_UID, $info['fUid']);
            return $result;
        }
        // 添加备注缓存
        if(!empty($result)){
            $cache = json_encode(array('r'=>$data['remark_name']));
            $this->diaryListCacheModel->addRmask(AC::HOST_UID, $info['fUid'], $cache);
        }
        return $result;
    }
    
}

